/*

    tools23d - tools for converting images to 3D formats.
    Copyright (C) 2014  Dave Gorst

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.

*/

/**
 * @file   btime23d.c
 * @brief  Main entry point to btime23d code called from main().
 *
 */


#include <ctype.h>
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <time.h>

#include "FreeImage.h"

#include "tools23d.h"
#include "btime23d.h"
#include "frameset.h"
#include "cli-common.h"
#include "cli-btime.h"
#include "glob-all.h"
#include "image-fi.h"
#include "image.h"
#include "util.h"

/**
@brief	Main btime23d function.

Main btime23d function, called from main ().

Syntax :

btime23d \<frame offset\> \<input file pattern\> \<output directory\> [options]

@return Return ::t3d_return code indicating status.
*/

t3d_return T3D_Run (params * cli_params)
{
	image_details target_details, first_frame_details;
	unsigned int frame, number_of_frames, number_of_files;
	int left_eye, right_eye;
	unsigned int my_globule;
	file_entry * left_eye_file;
	file_entry * right_eye_file;
	char * left_eye_filename;
	char * right_eye_filename;
	time_t change_time;
	char * write_filename;
	frame_plan * my_frames = NULL;
	BOOL success = TRUE;
	int current_input_filename = cli_params->number_of_input_filenames;
	
	my_globule = T3D_InitialiseGlob ();

	while (current_input_filename)
		T3D_PopulateGlob (my_globule, cli_params->input_filenames [--current_input_filename]);

	if ((number_of_files = T3D_GetNumberOfEntries (my_globule)))
	{
		T3D_RetrievePictureDetails (T3D_RetrieveGlobEntry (my_globule, 0)->filepath, &first_frame_details.format, &first_frame_details.width, &first_frame_details.height, &first_frame_details.depth);

		if ((!cli_params->width) && (!cli_params->height))
		{
			target_details.width = first_frame_details.width;
			target_details.height = first_frame_details.height;
		}
		else
		{
			target_details.width = cli_params->width;
			target_details.height = cli_params->height;

		}
		target_details.depth = first_frame_details.depth;

		if (!T3D_InitialiseImageHandling(&target_details, cli_params->filter, cli_params->loglevel))
		{
			T3D_SetLastError("Couldn't initialise image library.");
			return t3d_bad_parameter;
		}

		target_details.format = T3D_RetrievePictureType (cli_params->output_filename);

		if (target_details.format == IMAGE_FORMAT_UNKNOWN)
		{
			T3D_SetLastError ("WARNING : Output image format could not be determined. Using input type.\n\n");
			target_details.format = first_frame_details.format;
		}

		if (T3D_CreateFrameset (cli_params, number_of_files, &number_of_frames, &my_frames) == t3d_success)
		{
			for (frame = 0; ((frame < number_of_frames) && (success)); frame ++)
			{
				left_eye = my_frames[frame].left;
				right_eye = my_frames[frame].right;

				left_eye_file = T3D_RetrieveGlobEntry (my_globule, left_eye);
				right_eye_file = T3D_RetrieveGlobEntry (my_globule, right_eye);

				change_time = cli_params->frame_offset <= 0 ?
					left_eye_file->change_time :
					right_eye_file->change_time;

				write_filename = T3D_ProcessWriteFilename(cli_params->output_filename, frame, change_time);

				if ((success = ((write_filename != (char *) NULL) ? TRUE : FALSE)))
				{

					left_eye_filename = left_eye_file->filepath;
					right_eye_filename = right_eye_file->filepath;

					success = T3D_Write3DImage
					(
						left_eye_filename,
						right_eye_filename,
						write_filename,
						&target_details,
						cli_params->mode,
						cli_params->filter,
						cli_params->croptype,
						cli_params->preserve_aspect_ratio,
						cli_params->loglevel,
						100
					);
				}
				else
					T3D_SetLastError ("Malformed file time or format specifier when trying to create output filename.");
			}
		}
		else
			T3D_SetLastError ("Unable to create frameset.");
	}
	else
		T3D_SetLastError ("Nothing to do!");

	T3D_DestroyFrameset (&my_frames);

	T3D_ShutdownImageHandling();

	T3D_ShutdownGlob ();

	return (T3D_CheckForError());
}
